From c0b2433fa9c97b2c299c4905254c8d4bd285bc39 Mon Sep 17 00:00:00 2001 From: "kaf24@firebug.cl.cam.ac.uk" Date: Tue, 25 Apr 2006 14:20:08 +0100 Subject: [PATCH] Change the xenbus_map_ring_valloc() interface and implementation so that it is buildable as a module. Signed-off-by: Jan Beulich --- .../drivers/xen/pciback/pciback.h | 1 + .../drivers/xen/pciback/xenbus.c | 15 +++++--- .../xen/xenbus/xenbus_backend_client.c | 35 ++++--------------- linux-2.6-xen-sparse/include/xen/xenbus.h | 6 ++-- 4 files changed, 21 insertions(+), 36 deletions(-) diff --git a/linux-2.6-xen-sparse/drivers/xen/pciback/pciback.h b/linux-2.6-xen-sparse/drivers/xen/pciback/pciback.h index aaa0d75d3a..77d63e0030 100644 --- a/linux-2.6-xen-sparse/drivers/xen/pciback/pciback.h +++ b/linux-2.6-xen-sparse/drivers/xen/pciback/pciback.h @@ -29,6 +29,7 @@ struct pciback_device { int evtchn_irq; + struct vm_struct *sh_area; struct xen_pci_sharedinfo *sh_info; }; diff --git a/linux-2.6-xen-sparse/drivers/xen/pciback/xenbus.c b/linux-2.6-xen-sparse/drivers/xen/pciback/xenbus.c index dc369d0efb..f073b35679 100644 --- a/linux-2.6-xen-sparse/drivers/xen/pciback/xenbus.c +++ b/linux-2.6-xen-sparse/drivers/xen/pciback/xenbus.c @@ -26,6 +26,7 @@ static struct pciback_device *alloc_pdev(struct xenbus_device *xdev) spin_lock_init(&pdev->dev_lock); + pdev->sh_area = NULL; pdev->sh_info = NULL; pdev->evtchn_irq = INVALID_EVTCHN_IRQ; pdev->be_watching = 0; @@ -48,7 +49,7 @@ static void free_pdev(struct pciback_device *pdev) unbind_from_irqhandler(pdev->evtchn_irq, pdev); if (pdev->sh_info) - xenbus_unmap_ring_vfree(pdev->xdev, pdev->sh_info); + xenbus_unmap_ring_vfree(pdev->xdev, pdev->sh_area); pciback_release_devices(pdev); @@ -63,15 +64,19 @@ static int pciback_do_attach(struct pciback_device *pdev, int gnt_ref, { int err = 0; int evtchn; + struct vm_struct *area; + dev_dbg(&pdev->xdev->dev, "Attaching to frontend resources - gnt_ref=%d evtchn=%d\n", gnt_ref, remote_evtchn); - err = - xenbus_map_ring_valloc(pdev->xdev, gnt_ref, - (void **)&pdev->sh_info); - if (err) + area = xenbus_map_ring_valloc(pdev->xdev, gnt_ref); + if (IS_ERR(area)) { + err = PTR_ERR(area); goto out; + } + pdev->sh_area = area; + pdev->sh_info = area->addr; err = xenbus_bind_evtchn(pdev->xdev, remote_evtchn, &evtchn); if (err) diff --git a/linux-2.6-xen-sparse/drivers/xen/xenbus/xenbus_backend_client.c b/linux-2.6-xen-sparse/drivers/xen/xenbus/xenbus_backend_client.c index 398541a1f3..e7a018389c 100644 --- a/linux-2.6-xen-sparse/drivers/xen/xenbus/xenbus_backend_client.c +++ b/linux-2.6-xen-sparse/drivers/xen/xenbus/xenbus_backend_client.c @@ -30,21 +30,20 @@ * IN THE SOFTWARE. */ +#include #include #include #include /* Based on Rusty Russell's skeleton driver's map_page */ -int xenbus_map_ring_valloc(struct xenbus_device *dev, int gnt_ref, void **vaddr) +struct vm_struct *xenbus_map_ring_valloc(struct xenbus_device *dev, int gnt_ref) { struct gnttab_map_grant_ref op; struct vm_struct *area; - *vaddr = NULL; - area = alloc_vm_area(PAGE_SIZE); if (!area) - return -ENOMEM; + return ERR_PTR(-ENOMEM); gnttab_set_map_op(&op, (unsigned long)area->addr, GNTMAP_host_map, gnt_ref, dev->otherend_id); @@ -58,14 +57,14 @@ int xenbus_map_ring_valloc(struct xenbus_device *dev, int gnt_ref, void **vaddr) xenbus_dev_fatal(dev, op.status, "mapping in shared page %d from domain %d", gnt_ref, dev->otherend_id); - return op.status; + BUG_ON(!IS_ERR(ERR_PTR(op.status))); + return ERR_PTR(op.status); } /* Stuff the handle in an unused field */ area->phys_addr = (unsigned long)op.handle; - *vaddr = area->addr; - return 0; + return area; } EXPORT_SYMBOL_GPL(xenbus_map_ring_valloc); @@ -92,30 +91,10 @@ EXPORT_SYMBOL_GPL(xenbus_map_ring); /* Based on Rusty Russell's skeleton driver's unmap_page */ -int xenbus_unmap_ring_vfree(struct xenbus_device *dev, void *vaddr) +int xenbus_unmap_ring_vfree(struct xenbus_device *dev, struct vm_struct *area) { - struct vm_struct *area; struct gnttab_unmap_grant_ref op; - /* It'd be nice if linux/vmalloc.h provided a find_vm_area(void *addr) - * method so that we don't have to muck with vmalloc internals here. - * We could force the user to hang on to their struct vm_struct from - * xenbus_map_ring_valloc, but these 6 lines considerably simplify - * this API. - */ - read_lock(&vmlist_lock); - for (area = vmlist; area != NULL; area = area->next) { - if (area->addr == vaddr) - break; - } - read_unlock(&vmlist_lock); - - if (!area) { - xenbus_dev_error(dev, -ENOENT, - "can't find mapped virtual address %p", vaddr); - return GNTST_bad_virt_addr; - } - gnttab_set_unmap_op(&op, (unsigned long)vaddr, GNTMAP_host_map, (grant_handle_t)area->phys_addr); diff --git a/linux-2.6-xen-sparse/include/xen/xenbus.h b/linux-2.6-xen-sparse/include/xen/xenbus.h index b5a9da5f64..ab0c59df76 100644 --- a/linux-2.6-xen-sparse/include/xen/xenbus.h +++ b/linux-2.6-xen-sparse/include/xen/xenbus.h @@ -228,8 +228,8 @@ int xenbus_grant_ring(struct xenbus_device *dev, unsigned long ring_mfn); * or -ENOMEM on error. If an error is returned, device will switch to * XenbusStateClosing and the error message will be saved in XenStore. */ -int xenbus_map_ring_valloc(struct xenbus_device *dev, - int gnt_ref, void **vaddr); +struct vm_struct *xenbus_map_ring_valloc(struct xenbus_device *dev, + int gnt_ref); int xenbus_map_ring(struct xenbus_device *dev, int gnt_ref, grant_handle_t *handle, void *vaddr); @@ -241,7 +241,7 @@ int xenbus_map_ring(struct xenbus_device *dev, int gnt_ref, * Returns 0 on success and returns GNTST_* on error * (see xen/include/interface/grant_table.h). */ -int xenbus_unmap_ring_vfree(struct xenbus_device *dev, void *vaddr); +int xenbus_unmap_ring_vfree(struct xenbus_device *dev, struct vm_struct *); int xenbus_unmap_ring(struct xenbus_device *dev, grant_handle_t handle, void *vaddr); -- 2.30.2